package com.atguigu.gulimall.search.thread;

import com.sun.javafx.logging.PulseLogger;

import javax.xml.bind.SchemaOutputResolver;
import java.util.concurrent.CompletableFuture;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;


/*
*
*   任务并行执行:
*   任务串行:
*        有n个任务，任务3需要在任务2执行完后或拿到任务2的返回结果才可以执行
*   任务组合: 至少3个任务的场景
*       任务1，2执行完后 任务3 才可以执行
*
* */
public class ThreadTest {

    public static ExecutorService executor = Executors.newFixedThreadPool(10);

    public static void main(String[] args) throws  Exception {

       /* CompletableFuture<Void> future = CompletableFuture.runAsync(()->{
            System.out.println("当前线程: "+ Thread.currentThread().getId());
            int i =10/2;
            System.out.println("运行结果: "+i);
        },executor);
        //supplyAsync 是带返回结果的
        CompletableFuture<Integer> future1 = CompletableFuture.supplyAsync(()->{
            System.out.println("当前线程: "+ Thread.currentThread().getId());
            int i =10/2;
            System.out.println("运行结果: "+i);
            return i;},executor);
        Integer integer = future1.get();*
        */
/***************************************************************************************/
       /* whenComplete： 其中的参数是 前面参数是结果，后面异常
        exceptionally :感知异常同时返回默认值*/
       /* CompletableFuture<Integer> future3 = CompletableFuture.supplyAsync(()->{
            System.out.println("当前线程: "+ Thread.currentThread().getId());
            int i =10/2;
            System.out.println("运行结果: "+i);
            return i;},executor).whenComplete((res,excp)->{
            System.out.println("异步任务完成了 结果是 "+res+"异常是: "+excp);
        }).exceptionally((throwabl)->{
            return 10; });*
 /***************************************************************************************/
      /* //用handle来处理返回结果
       CompletableFuture<Integer> future4 = CompletableFuture.supplyAsync(() -> {
            System.out.println("当前线程: " + Thread.currentThread().getId());
            int i = 10 / 2;
            System.out.println("运行结果: " + i);
            return i;
        }, executor).whenComplete((res, excp) -> {
            System.out.println("异步任务完成了 结果是 " + res + "异常是: " + excp);
        }).handle((res, thr) -> {
            System.out.println("返回一个值return 1");
            return 1;
        });*
  /***************************************************************************************/
   /* 线程串行化 即 1，2，3 线程并行执行，4，5等到1 执行完后 拿到结果才可以执行
        thenRu(Runnable)n: 不需要接受前面线程的返回值
        thenAccept(Consumer<? super T>) : 需要接受前面线程的返回值
        thenApply(Function<? super T,? extends U>):   需要接受前面线程的返回值 并且还要再传递自己的结果给下一个线程
        */
        /* CompletableFuture.supplyAsync(() -> {
            int i = 10 / 2;
            return i;
        }, executor).thenRunAsync(()->{
            System.out.println("thenRun是不会取到上一步执行的结果的，要结果请求thenAccept");
        },executor);
        //C199
        CompletableFuture.supplyAsync(() -> {
            return 10;
        }, executor).thenAcceptAsync((res)->{
            System.out.println("thenAcceptAsync可以接受上一步的返回值 但自己这步无返回值");
        },executor);*/
/***************************************************************************************/
            //两任务组合 即 任务1，2执行完后 再执行 任务3
          /*   runAfterBoth:   前两个任务执行完后 载执行任务3
             thenAcceptBoth: 可以获取前两个任务的返回结果
              thenCombine: 可以获取前两个任务的返回结果 并将可以自己的结果返回出去*/
        CompletableFuture<Integer>
                f1 = CompletableFuture.supplyAsync(()->{
                    int i =10/2; return i; },executor);
        CompletableFuture<Integer>
                f2 = CompletableFuture.supplyAsync(()->{
                     int i =100/2; return i; },executor);
        //前两个任务执行完后 执行第3个任务
        f1.runAfterBothAsync(f2,()->{
            System.out.println("f1 f2执行完后执行 任务3 (不接受前两任务的返回值)");
        });
        //前两个任务执行完后 执行第3个任务 (接受前两个任务的返回值)
        f1.thenAcceptBothAsync(f2,(res1,res2)->{
            System.out.println("1 f2执行完后执行 任务3 (接受前两个任务的返回值)");
        },executor);
        //拿到f1和f2的的返回值 在任务3中执行完 再将返回值返回出去
        f1.thenCombineAsync(f2,(res1,res2)->{
            System.out.println("1 f2执行完后执行 任务3 (接受前两个任务的返回值，并将返回值返回出去) ");
            return  res1+ res2; },executor);

        //两个任务只要一个完成就执行第3个任务
        f1.runAfterEitherAsync(f2,()->{
            System.out.println("前两任务任意一个结束 就执行第3个任务(不接受前面任务的结果)");
           },executor);
        f1.acceptEitherAsync(f2,(res)->{
            System.out.println("前两任务任意一个结束  就执行第3个任务(受前面任务的结果)");
        },executor);
        f1.applyToEitherAsync(f2,(res)->{
            System.out.println("前两任务任意一个结束  就执行第3个任务(受前面任务的结果)，并发返回结果" );
            return 11;
        },executor);

/***************************************************************************************/



    }
}
